using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Data;
using System.Text;
using System.Windows.Forms;
using SBPweb.Localization;
using SBPweb.Presentation.Windows.Forms.Controls;
using Verety.SharedMeta.DirectoryServiceMeta.Conversation.ChatHistory;
using System.Runtime.Serialization;
using System.Collections;
using System.IO;
using SBPweb.Modules.Modularity;

namespace SBPweb.Modules.ContactsManager.Controls
{
	public partial class ViewHistoryControl : ModalDockingUserControl
	{
		#region Private members

		private IFormatter formatter;
		private ArrayList entryList = new ArrayList();
		private DataSet dataset = new DataSet();
		private DataTable dt = new DataTable("History");
		private ContactListControl mContactListControl;
		private string mContactJID;
		private string mFullPath;

		private enum ElementType { Other, TimeStamp, To, From, Packet };

		#endregion

		#region Constructor logic

		public ViewHistoryControl(ContactListControl contactListControl, string contactJID, string fullPath)
			: base(contactListControl.ParentModule)
		{
			mContactListControl = contactListControl;
			mContactJID = contactJID;
			mFullPath = fullPath;
			InitializeComponent();
			this.MinimumSize = FloatingSize = new Size(536, 362);

			LocalizationExtender.OnInvalidatedControls += new EventHandler(LocalizationExtender_OnInvalidatedControls);

			dt.Columns.Add("Time");
			dt.Columns.Add("From");
			dt.Columns.Add("To");
			dt.Columns.Add("Message");
			dataset.Tables.Add(dt);

			FillFromFile();

			this.Caption = string.Format(LocalizationExtender.GetString("ChatHistoryHeader"), contactJID);
			gridControl.DataSource = dataset;
			gridControl.DataMember = "History";
			gcTime.FieldName = "Time";
			gcTime.Caption = LocalizationExtender.GetString("ChatHistoryTimeHeader");
			gcFrom.FieldName = "From";
			gcFrom.Caption = LocalizationExtender.GetString("ChatHistoryFromHeader");
			gcTo.FieldName = "To";
			gcTo.Caption = LocalizationExtender.GetString("ChatHistoryToHeader");
			gcMessage.FieldName = "Message";
			gcMessage.Caption = LocalizationExtender.GetString("ChatHistoryMessageHeader");
			gridView.FocusRectStyle = DevExpress.XtraGrid.Views.Grid.DrawFocusRectStyle.RowFocus;
			gridControl.Refresh();

			gridView.Columns["Time"].OptionsColumn.AllowEdit = false;
			gridView.Columns["Time"].OptionsColumn.AllowFocus = false;
			gridView.Columns["Time"].OptionsColumn.AllowGroup = DevExpress.Utils.DefaultBoolean.False;
			gridView.Columns["Time"].OptionsColumn.ReadOnly = true;
			gridView.Columns["From"].OptionsColumn.AllowEdit = false;
			gridView.Columns["From"].OptionsColumn.AllowFocus = false;
			gridView.Columns["From"].OptionsColumn.AllowGroup = DevExpress.Utils.DefaultBoolean.True;
			gridView.Columns["From"].OptionsColumn.ReadOnly = true;
			gridView.Columns["To"].OptionsColumn.AllowEdit = false;
			gridView.Columns["To"].OptionsColumn.AllowFocus = false;
			gridView.Columns["To"].OptionsColumn.AllowGroup = DevExpress.Utils.DefaultBoolean.True;
			gridView.Columns["To"].OptionsColumn.ReadOnly = true;
			gridView.Columns["Message"].OptionsColumn.AllowEdit = false;
			gridView.Columns["Message"].OptionsColumn.AllowFocus = false;
			gridView.Columns["Message"].OptionsColumn.AllowGroup = DevExpress.Utils.DefaultBoolean.False;
			gridView.Columns["Message"].OptionsColumn.ReadOnly = true;

			setInfo(LocalizationExtender.GetString("ChatHistoryLoadingMessage"));

			gridView.GroupPanelText = string.Format(LocalizationExtender.GetString("GroupPanelText"), LocalizationExtender.GetString("ChatHistoryFromHeader"), LocalizationExtender.GetString("ChatHistoryToHeader"));

			if (this.Parent != null)
			{
				this.Parent.Resize += new EventHandler(Parent_Resize);
			}

			this.Dock = DockStyle.Fill;
		}

		#endregion

		#region Event handlers

		private void LocalizationExtender_OnInvalidatedControls(object sender, EventArgs e)
		{
			this.Caption = string.Format(LocalizationExtender.GetString("ChatHistoryHeader"), mContactJID);
			gcTime.Caption = LocalizationExtender.GetString("ChatHistoryTimeHeader");
			gcFrom.Caption = LocalizationExtender.GetString("ChatHistoryFromHeader");
			gcTo.Caption = LocalizationExtender.GetString("ChatHistoryToHeader");
			gcMessage.Caption = LocalizationExtender.GetString("ChatHistoryMessageHeader");
			gridView.GroupPanelText = string.Format(LocalizationExtender.GetString("GroupPanelText"), LocalizationExtender.GetString("ChatHistoryFromHeader"), LocalizationExtender.GetString("ChatHistoryToHeader"));
			Parent_Resize(sender, e);

			foreach (object o in gridView.Columns)
			{
			}
		}

		private void Parent_Resize(object sender, EventArgs e)
		{
			this.Size = this.Parent.ClientSize;
			this.pnlInfo.Width = this.pnlGrid.Width = this.Width;
			this.pnlGrid.Height = this.Height - this.pnlInfo.Height;
			this.gridControl.Size = pnlGrid.Size;
			this.btnClose.Location = new Point(this.pnlInfo.Width - 5 - this.btnClose.Width, this.pnlInfo.Height - 5 - this.btnClose.Height);
		}

		private void btnClose_Click(object sender, EventArgs e)
		{
			mContactListControl.ParentModule.Host.Smartparts.Remove(this);
		}

		#endregion

		#region Private methods

		private void FillFromFile()
		{
			try
			{
				dt.Rows.Clear();

				entryList = new ArrayList();

				if (!(mContactListControl.DirectoryService.Conversations is Verety.SharedMeta.DirectoryServiceMeta.Conversation.IDirectoryConversationManager))
				{
					return;
				}

				formatter = (mContactListControl.DirectoryService.Conversations as Verety.SharedMeta.DirectoryServiceMeta.Conversation.IDirectoryConversationManager).CreateHistoryEntryFormatter();

				if (checkFile())
				{
					List<IHistoryEntry> entries = GetMessages();

					foreach (IHistoryEntry entry in entries)
					{
						DataRow dr = dt.NewRow();
						dr["Time"] = entry.Timestamp.ToString("yyyy. MMM dd. HH:mm:ss");
						dr["From"] = entry.FromUser;
						dr["To"] = entry.ToUser;
						dr["Message"] = entry.Message;
						dt.Rows.Add(dr);
					}
				}

				FileInfo f = new FileInfo(mFullPath);
				setInfo(string.Format(LocalizationExtender.GetString("ChatHistoryRecordNumber"), dt.Rows.Count));

				DevExpress.XtraGrid.StyleFormatCondition styleFormatCondition1 = new DevExpress.XtraGrid.StyleFormatCondition();
				DevExpress.XtraGrid.StyleFormatCondition styleFormatCondition2 = new DevExpress.XtraGrid.StyleFormatCondition();

				styleFormatCondition1.Appearance.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(255)))), ((int)(((byte)(255)))), ((int)(((byte)(128)))));
				styleFormatCondition1.Appearance.BackColor2 = System.Drawing.Color.FromArgb(((int)(((byte)(255)))), ((int)(((byte)(255)))), ((int)(((byte)(128)))));
				styleFormatCondition1.Appearance.Options.UseBackColor = true;
				styleFormatCondition1.ApplyToRow = true;
				styleFormatCondition1.Column = this.gcFrom;
				styleFormatCondition1.Condition = DevExpress.XtraGrid.FormatConditionEnum.Equal;
				styleFormatCondition1.Value1 = mContactListControl.DirectoryService.Connection.UserName;

				this.gridView.FormatConditions.Clear();
				this.gridView.FormatConditions.AddRange(new DevExpress.XtraGrid.StyleFormatCondition[] { styleFormatCondition1 });
			}
			catch (Exception ex)
			{
				if (ParentModule != null)
				{
					ParentModule.Host.LogManager.WriteInfo(this, string.Format("Cannot open chat history.\n{0}", ex.Message), "ChatController");
				}
				dt.Rows.Clear();
				setInfo(LocalizationExtender.GetString("ChatHistoryCorruptFileLine"));
				lblChatOwner.Text = string.Empty;
				lblContact.Text = string.Empty;
				lblRoute.Text = string.Empty;
			}
		}

		private List<IHistoryEntry> GetMessages()
		{
			int c = this.entryList.Count;
			List<IHistoryEntry> entries = new List<IHistoryEntry>();

			for (int i = 0; i < c; i++)
			{
				entries.Add((IHistoryEntry)entryList[entryList.Count - c + i]);
			}

			return entries;
		}

		private void setInfo(string text)
		{
			lblInfo.Text = text;
		}

		private bool checkFile()
		{
			string owner = "";
			string contact = "";
			string route = "";

			if (System.IO.File.Exists(mFullPath))
			{
				System.IO.Stream stream;
				System.IO.MemoryStream memStream;
				System.IO.TextReader reader;
				System.IO.TextWriter writer;
				string line;

				stream = new System.IO.FileStream(mFullPath, System.IO.FileMode.Open, System.IO.FileAccess.Read);
				memStream = new System.IO.MemoryStream();
				reader = new System.IO.StreamReader(stream);
				writer = new System.IO.StreamWriter(memStream);

				try
				{
					IHistoryEntry historyEntry;

					bool inNode = false;

					while ((line = reader.ReadLine()) != null)
					{
						if (!inNode)
						{
							if (line.StartsWith("</HistoryEntry>"))
							{ }
							else if (line.StartsWith("<HistoryEntry>"))
							{
								inNode = true;
								writer.Write(line);
							}
							else if (line.ToLower().StartsWith("<history "))
							{
								if (line.Contains("owner="))
								{
									string tmp = line.Substring(line.IndexOf("owner=") + 1 + "owner=".Length);
									owner = tmp.Substring(0, tmp.IndexOf("'"));
								}
								if (line.Contains("contact="))
								{
									string tmp = line.Substring(line.IndexOf("contact=") + 1 + "contact=".Length);
									contact = tmp.Substring(0, tmp.IndexOf("'"));
								}
								if (line.Contains("routeAddress="))
								{
									string tmp = line.Substring(line.IndexOf("routeAddress=") + 1 + "routeAddress=".Length);
									route = tmp.Substring(0, tmp.IndexOf("'"));
								}
								lblChatOwner.Text = owner;
								lblContact.Text = contact;
								lblRoute.Text = route;
							}
							continue;
						}
						else
						{
							if (line.StartsWith("<HistoryEntry>"))
							{ }
							else if (line.StartsWith("</HistoryEntry>"))
							{
								inNode = false;
								writer.Write(line);
								writer.Flush();
							}
							else
							{
								writer.Write(line);
								continue;
							}
						}

						memStream.Seek(0, System.IO.SeekOrigin.Begin);
						historyEntry = (IHistoryEntry)formatter.Deserialize(memStream);
						memStream.SetLength(0);

						if (historyEntry != null)
						{
							entryList.Add(historyEntry);
						}
						else
						{
							return false;
						}
					}

					return true;
				}
				catch (Exception ex)
				{
					ParentModule.Host.LogManager.WriteInfo(this, string.Format("Error during check chat history.\n{0}", ex.Message), "ChatController");
					return false;
				}
				finally
				{
					reader.Close();
					writer.Close();
					memStream.Close();
					stream.Close();
				}
			}
			else
			{
				return false;
			}
		}

		#endregion
	}
}
